package Data::Conveyor::Charset::ViaHash;

# $Id: ViaHash.pm 13653 2007-10-22 09:11:20Z gr $

use strict;
use warnings;
use charnames ':full';


our $VERSION = '0.02';


use base 'Data::Conveyor::Charset';


__PACKAGE__
    ->mk_singleton_constructor(qw(new))
    ->mk_hash_accessors(qw(character_cache))
    ->mk_scalar_accessors(qw(valid_string_re_cache));


sub CHARACTERS { () }


sub get_characters {
    my $self = shift;
    unless ($self->character_cache_keys) {

        my $characters = $self->every_hash('CHARACTERS');

        # Convert the hash values to their actual Unicode character
        # equivalent. For defining a character, we accept Unicode character
        # names (the "..." part of the "\N{...}" notation) or hex code points
        # (indicated by a leading "0x"; useful for characters that don't have
        # a name).

        for (values %$characters) {
            if (/^0x(.*)$/) {
                $_ = sprintf '%c' => hex($1);
            } else {
                $_ = sprintf '%c' => charnames::vianame($_);
            }
            utf8::upgrade($_);
        }

        $self->character_cache(%$characters);
    }
    return $self->character_cache;
}


sub get_character_names {
    my $self = shift;
    my %characters = $self->get_characters;
    my @names = keys %characters;
    wantarray ? @names : \@names;
}


sub get_character_values {
    my $self = shift;
    my %characters = $self->get_characters;
    my @values = values %characters;
    wantarray ? @values : \@values;
}


sub is_valid_string {
    my ($self, $string) = @_;

    unless (defined $self->valid_string_re_cache) {

        # escape critical characters so they're not interpreted as special
        # characters in the regex.

        my $chars = join '', map {
            m{^[\-.+*?()\[\]/\\]$} ? sprintf("\\%s", $_ ) : $_;
        } $self->get_character_values;

        $self->valid_string_re_cache(qr/^[$chars]+$/);
    }

    $string =~ $self->valid_string_re_cache;
}


1;


__END__

{% USE p = PodGenerated %}

=head1 NAME

{% p.package %} - stage-based conveyor-belt-like ticket handling system

=head1 SYNOPSIS

    {% p.package %}->new;

=head1 DESCRIPTION

None yet. This is an early release; fully functional, but undocumented. The
next release will have more documentation.

=head1 METHODS

=over 4

{% p.write_methods %}

=back

{% p.write_inheritance %}

{% PROCESS standard_pod %}

=cut

